package org.sokolenko.regexp;

import com.intellij.codeInsight.intention.IntentionAction;
import com.intellij.openapi.editor.Editor;
import com.intellij.openapi.project.Project;
import com.intellij.psi.PsiFile;
import com.intellij.psi.PsiElement;
import com.intellij.util.IncorrectOperationException;
import com.intellij.lang.Language;
import org.jetbrains.annotations.NotNull;

/**
 * @author Anatoliy Sokolenko
 *         1 серп 2009 0:48:19
 */
public class EvaluationIntention implements IntentionAction {
    private static final String INTENTION_TEXT = "Evaluate regular expression";
    private static final String INTENTION_FAMILY = "Regular Expressions";

    @NotNull
    public String getText() {
        return INTENTION_TEXT;
    }

    @NotNull
    public String getFamilyName() {
        return INTENTION_FAMILY;
    }

    public boolean isAvailable( @NotNull Project project, Editor editor, PsiFile psiFile ) {
        final Language regExpLanguage = Language.findLanguageByID( "RegExp" );
        final int offset = editor.getCaretModel().getOffset();

        PsiElement element = psiFile.findElementAt( offset );

        if (element != null) {
            Language currentLanguage = element.getLanguage();

            if ( currentLanguage.is( regExpLanguage ) ) {
                return true;
            } else {
                return false;
            }
        } else {
            return false;
        }
    }

    public void invoke( @NotNull Project project, Editor editor, PsiFile psiFile ) throws IncorrectOperationException {
        int offset = editor.getCaretModel().getOffset();
        PsiElement element = psiFile.findElementAt( offset );

        CharSequence text = editor.getDocument().getCharsSequence();
        String expression = getStringAtCaret( offset, text );

        EvaluationProjectComponent evaluationComponent = project.getComponent( EvaluationProjectComponent.class );
        evaluationComponent.showEvaluationForm( expression, editor );
    }

    public boolean startInWriteAction() {
        return true;
    }

    private String getStringAtCaret( int offset, CharSequence text ) {
        int start = 0;
        for ( int i = offset; i >= 0; i-- ) {
            if ( text.charAt( i ) == '"'
                    && ( ( i > 0 && text.charAt( i - 1 ) != '\\' ) || ( i == 0 ) ) ) {
                start = i + 1;
                break;
            }
        }

        int end = 0;
        for ( int i = offset; i < text.length(); i++ ) {
            if ( text.charAt( i ) == '"'
                    && ( ( i + 1 < text.length() && text.charAt( i - 1 ) != '\\' ) || ( i == 0 ) ) ) {
                end = i;
                break;
            }
        }

        return text.subSequence( start, end ).toString();
    }
}
